#include "SCAN.h"
#include "ui_scan.h"

#define WIDTH 1200
#define HEIGHT 800
#define LENGTH 400
#define TOTAL_STATION 9
#define DISTANCE 2


QVector<QString>head;
QVector<QVector<int>> array; //输出的数组
QVector<QVector<int>> waittime; //等待时间
int curtime; //计时器
bus Bus;
QString s;

int x_1 = 100;
int y_1 = 180;
int x_2 = x_1 + LENGTH;
int y_2 = y_1 + LENGTH;
int distance = LENGTH * 4 / (TOTAL_STATION * DISTANCE);
int bus_x = x_1;
int bus_y = y_1;


int first = 1;
int init_status = -1;
int key = 0;
int checkdirection = -1;




//构造函数
SCAN::SCAN(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::SCAN)
{
    ui->setupUi(this);
    ui->bus->installEventFilter(this);
    setFixedSize(1200,800);
    //创建数组，并完成初始化
    array.resize(3);
    for(int j=0;j<array.size();j++)
    {
        array[j].resize(TOTAL_STATION+2);
    }
    waittime.resize(3);
    for(int j=0;j<waittime.size();j++)
    {
        waittime[j].resize(TOTAL_STATION);
    }
    //设置当前时间
    Bus.position=0;
    Bus.status = 1; //先将公交设置为可以接受请求的状态
    curtime=0;
    //label中填充图片
    QImage Image;
    Image.load(":/img/bus.png");
    QPixmap pixmap = QPixmap::fromImage(Image);
    int with = ui->label->width();
    int height = ui->label->height();
    QPixmap fitpixmap = pixmap.scaled(with, height, Qt::KeepAspectRatio, Qt::SmoothTransformation);  // 按比例缩放
    ui->label->setPixmap(fitpixmap);
    ui->label->move(QPoint(bus_x,bus_y));
    ui->state->setText("等待请求中...");
    QPixmap p;
    p.load(":/img/flower.png");
    p.scaled(ui->icon->size(), Qt::KeepAspectRatio);
    ui->icon->setScaledContents(true);
    ui->icon->setPixmap(p);


    //链接槽函数和信号（点击按钮将文本框中输入的内容取得）
    connect(ui->TButton,&QPushButton::clicked,this,&SCAN::TchangArr);
    connect(ui->CButton,&QPushButton::clicked,this,&SCAN::CchangArr);
    connect(ui->UButton,&QPushButton::clicked,this,&SCAN::UchangArr);
    //设置定时器
    startTimer(1500);
}

//下面两个函数用于在左侧的label中绘制矩形，在画边界的时候比较费脑子
bool SCAN::eventFilter(QObject *watched, QEvent *event) {
    if (watched == ui->bus && event->type() == QEvent::Paint) {
        paintbus();
    }
    return QWidget::eventFilter(watched, event);
}

void SCAN::paintbus() {

    QPainter painter(ui->bus);

    //绘制矩形
    QPen pen(QColor(200, 200, 200));
    pen.setWidth(7);
    painter.setPen(pen);
    int margin_left=100;
    int margin_top=(HEIGHT-LENGTH)/2;
    QRectF rectangle(margin_left,margin_top, LENGTH, LENGTH);  //坐标，宽高
    painter.drawRect(rectangle);
    //绘制上面的点
    int x=margin_left;
    int y=margin_top;
    int flag=1;
    for(int i=0;i<TOTAL_STATION * DISTANCE; i++)
    {
        if (i % DISTANCE)
        {
            painter.setPen(QColor(Qt::black));
            painter.setBrush(QBrush(Qt::black));
            painter.drawEllipse(x-4,y-4,7,7);
        }
        else {
            painter.setPen(QColor(Qt::red));
            painter.setBrush(QBrush(Qt::red));
            painter.drawEllipse(x-4,y-4,13,13);
        }

        if(flag==1&&LENGTH-(x-margin_left)<=distance){
            y+=distance-(LENGTH-(x-margin_left));
            x=margin_left+LENGTH;
            flag=2;

        }
        else if(flag==1&&LENGTH-(x-margin_left)>distance){
            x+=distance;

        }
        else if(flag==2&&LENGTH-(y-margin_top)<=distance)
        {
            x-=distance-(LENGTH-(y-margin_top));
            y=margin_top+LENGTH;
            flag=3;
        }
        else if(flag==2&&LENGTH-(y-margin_top)>distance)
        {
            y+=distance;
        }
        else if(flag==3&&(x-margin_left)<=distance)
        {
            y-=distance-(x-margin_left);
            x=margin_left;
            flag=4;
        }
        else if(flag==3&&(x-margin_left)>distance)
        {
            x-=distance;
        }
        else if(flag==4&&(y-margin_top)<=distance){
            y=margin_top;
            x+=distance-((y-margin_top));
            flag=1;
        }
        else if(flag==4&&(y-margin_top)>distance){
            y-=distance;
        }
    }
}



//点击按钮后收到数据并改变对应二进制数组
void SCAN::TchangArr(){
    QString temp=ui->Tedit->text();
    int station_num=temp.toInt();
    if (station_num!= 10)
    {
        if (Bus.status == 0 && Bus.position / DISTANCE + 1 == (station_num))
        {
            array[0][station_num - 1] = 0;
            array[1][station_num - 1] = 0;
            array[2][station_num - 1] = 0;
            return;
        }
        else if (key == 1 && Bus.position / DISTANCE + 1 == (station_num))
        {
            array[1][station_num - 1] = 0;
            array[2][station_num - 1] = 0;
            array[0][station_num - 1] = 0;
            return;
        }
        else
        {
            if (first == 1)
            {
                if(station_num == 1)
                {
                    array[1][0] = 0;
                    array[2][0] = 0;
                    array[0][0] = 0;
                    return;
                }
                else
                {
                    array[0][station_num - 1] = 1;
                    FirstSearch();
                    first = 0;
                    init_status = 1;
                }
            }
            else
            {
                array[0][station_num - 1] = 1;
            }
        }
    }
    else
    {
        if (Bus.status == 0 && Bus.position == 9 * DISTANCE)
        {
            array[0][9] = 0;
            array[1][9] = 0;
            array[2][9] = 0;
            return;
        }
        else if (key == 1 && Bus.position == 9 * DISTANCE)
        {
            array[1][9] = 0;
            array[2][9] = 0;
            array[0][9] = 0;
            return;
        }
        else
        {
            if (first == 1)
            {
                array[0][9] = 1;
                FirstSearch();
                first = 0;
                init_status = 1;
            }
            else
            {
                array[0][9] = 1;
            }
        }
    }
    ui->Tedit->clear();
}
void SCAN::CchangArr(){
    QString temp=ui->Cedit->text();
    int station_num=temp.toInt();
    if (station_num!=10)
    {
        if (Bus.status == 0 && Bus.position / DISTANCE + 1 == (station_num))
        {
            array[1][station_num - 1] = 0;
            array[2][station_num - 1] = 0;
            array[0][station_num - 1] = 0;
            return;
        }
        else if (key == 1 && Bus.position / DISTANCE + 1 == (station_num))
        {
            array[1][station_num - 1] = 0;
            array[2][station_num - 1] = 0;
            array[0][station_num - 1] = 0;
            return;
        }
        else
        {
            if (first == 1)
            {
                if(station_num == 1)
                {
                    array[1][0] = 0;
                    array[2][0] = 0;
                    array[0][0] = 0;
                    return;
                }
                else
                {
                    array[1][station_num - 1] = 1;
                    FirstSearch();
                    first = 0;
                    init_status = 1;
                }
            }
            else
            {
                array[1][station_num - 1] = 1;
            }
        }
    }
    else
    {
        if (Bus.status == 0 && Bus.position == 9 * DISTANCE)
        {
            array[1][9] = 0;
            array[2][9] = 0;
            array[0][9] = 0;
            return;
        }
        else if (key == 1 && Bus.position == 9 * DISTANCE)
        {
            array[1][9] = 0;
            array[2][9] = 0;
            array[0][9] = 0;
            return;
        }
        else
        {
            if (first == 1)
            {
                array[1][9] = 1;
                FirstSearch();
                first = 0;
                init_status = 1;
            }
            else
            {
                array[1][9] = 1;
            }
        }
    }
    ui->Cedit->clear();
}
void SCAN::UchangArr(){
    QString temp=ui->Uedit->text();
    int station_num=temp.toInt();
    if (station_num!=10)
    {
        if (Bus.status == 0 && Bus.position / DISTANCE + 1 == (station_num))
        {
            array[2][station_num - 1] = 0;
            array[1][station_num - 1] = 0;
            array[0][station_num - 1] = 0;
            return;
        }
        else if (key == 1 && Bus.position / DISTANCE + 1 == (station_num))
        {
            array[1][station_num - 1] = 0;
            array[2][station_num - 1] = 0;
            array[0][station_num - 1] = 0;
            return;
        }
        else
        {
            if (first == 1)
            {
                if(station_num == 1)
                {
                    array[1][0] = 0;
                    array[2][0] = 0;
                    array[0][0] = 0;
                    return;
                }
                else
                {
                    array[2][station_num - 1] = 1;
                    FirstSearch();
                    first = 0;
                    init_status = 1;
                }
            }
            else
            {
                array[2][station_num - 1] = 1;
            }
        }
    }
    else
    {
        if (Bus.status == 0 && Bus.position == 9 * DISTANCE)
        {
            array[2][9] = 0;
            array[1][9] = 0;
            array[0][9] = 0;
            return;
        }
        else if (key == 1 && Bus.position == 9 * DISTANCE)
        {
            array[1][9] = 0;
            array[2][9] = 0;
            array[0][9] = 0;
            return;
        }
        else
        {
            if (first == 1)
            {
                array[2][9] = 1;
                FirstSearch();
                first = 0;
                init_status = 1;
            }
            else
            {
                array[2][9] = 1;
            }

        }
    }
    ui->Uedit->clear();
}

//定时器
void SCAN::timerEvent(QTimerEvent *)
{
    curtime++;
    update();

}
//更新时间数组，
void SCAN::update(){
    output();
    if (key == 1)
    {
        key = 0;
    }

    if (init_status == 1)
    {
        init_status = 0;
        Bus.status = 1;
    }
    curtime++;
    int i = 0, flag = 0;
    for (i = 0; i < TOTAL_STATION; i++)
    {
        if (array[1][i] != 0 || array[2][i] != 0 || array[0][i] != 0)
        {
            flag = 1;
            break;
        }
        else
        {
            continue;
        }
    }
    if (flag == 0)
    {
        output();
        Bus.status = 1;
        key = 1;
        return;

    }
    else if (flag == 1)
    {
        if(checkdirection == 1)
        {
            DropBy(Bus.position/DISTANCE + 1);
            checkdirection = 0;
        }
        if (Bus.status == 1)//״̬
        {
            if (Bus.direction == 1)//
            {
                if (Bus.position == DISTANCE * TOTAL_STATION - 1)
                {
                    Bus.position = 0;
                }
                else
                {
                    Bus.position++;
                    shunshizhen();
                }
            }
            else if (Bus.direction == 2)
            {
                if (Bus.position == 0)
                {
                    Bus.position = TOTAL_STATION * DISTANCE - 1;
                }
                else
                {
                    Bus.position--;
                    nishizhen();
                }
            }

            if (Bus.position % DISTANCE == 0)
            {
                output();

                if (array[1][Bus.position / DISTANCE] == 1 || array[2][Bus.position / DISTANCE] == 1 || array[0][Bus.position / DISTANCE] == 1)
                {
                    array[1][Bus.position / DISTANCE] = 0;
                    array[2][Bus.position / DISTANCE] = 0;
                    array[0][Bus.position / DISTANCE] = 0;
                    Bus.status = 0;
                }
            }
            else if (Bus.position % DISTANCE != 0)
            {
                Bus.status = 1;
                output();
            }
        }
        else if(Bus.status == 0)
        {
            Bus.status = 1;
            checkdirection = 1;
            output();
            key = 1;
        }
    }
}

//输出
void SCAN::output(){
    static QString s;  //输出的字符串，将数组转化为字符串后输出在label中
    s="";
    head={"target:","clockwise:","counterclockwise:"};
    s+=QString("TIME:%1%2").arg(curtime).arg("\n");
    for(int i = 0; i < array.size(); i++)
    {
        s+=head[i];
        for (int  j= 0; j < TOTAL_STATION;j++)
        {
            QString temp;
            temp.setNum(array[i][j]);
            s+=temp;
        }
        s+="\n";
    }
    qDebug()<<s;
    ui->output_label->setText(s);

    QString b;
    b=QString::number(Bus.position);
    ui->pos->setText(b);
}


void SCAN::DropBy(int cur_station)
{
    int stationcount = 0;

    if (Bus.direction == 1)
    { //如果为顺时针方向行驶
        for (stationcount = 0; stationcount < TOTAL_STATION; stationcount++)
        {
            if (stationcount + cur_station > TOTAL_STATION)
            { //如果循环过程中超过了右边界
                if (array[1][stationcount + cur_station - TOTAL_STATION - 1] == 1 ||
                        array[2][stationcount + cur_station - TOTAL_STATION - 1] == 1 ||
                        array[0][stationcount + cur_station - TOTAL_STATION - 1] == 1)
                {
                    if (TOTAL_STATION / 2 < stationcount)
                    { //如果当前站点与当前方向上第一个有请求的站点的距离大于总站点数的一半
                        Bus.direction = 2; //切换行驶方向
                    }
                    break;
                }
            }
            else if (stationcount + cur_station <= TOTAL_STATION)
            { //如果循环过程中没有触碰到右边界
                if (array[1][stationcount + cur_station - 1] == 1 ||
                        array[2][stationcount + cur_station - 1] == 1 ||
                        array[0][stationcount + cur_station - 1] == 1)
                {
                    if (TOTAL_STATION / 2 < stationcount)
                    { //如果当前站点与当前方向上第一个有请求的站点的距离大于总站点数的一半
                        Bus.direction = 2; //切换行驶方向
                    }
                    break;
                }
            }
        }
    }
    else if (Bus.direction == 2)
    { //如果为逆时针方向行驶
        for (stationcount = 0; stationcount < TOTAL_STATION; stationcount++)
        {
            if (cur_station - stationcount > 0)
            {
                if (array[1][cur_station - stationcount - 1] == 1 ||
                        array[2][cur_station - stationcount - 1] == 1 ||
                        array[0][cur_station - stationcount - 1] == 1)
                {
                    if (TOTAL_STATION / 2 < stationcount)
                    {
                        Bus.direction = 1;
                    }
                    break;
                }
            }
            else if (cur_station - stationcount <= 0)
            {
                if (array[1][cur_station - stationcount + TOTAL_STATION - 1] == 1 ||
                        array[2][cur_station - stationcount + TOTAL_STATION - 1] == 1 ||
                        array[0][cur_station - stationcount + TOTAL_STATION - 1] == 1)
                {
                    if (TOTAL_STATION / 2 < stationcount)
                    {
                        Bus.direction = 1;
                    }
                    break;
                }
            }
        }
    }

    if (stationcount == TOTAL_STATION)
    { //如果没有请求，则将公交车状态改为静止
        Bus.status = 0;
    }
}

void SCAN::FirstSearch()
{
    int clockwise = TOTAL_STATION - 1, counterclockwise = TOTAL_STATION - 1;
    int i = 0;
    for (i = 1; i <= TOTAL_STATION - 1; i++)
    {
        if (array[2][i] == 1 || array[1][i] == 1 || array[0][i] == 1)
        {
            clockwise = i;
            break;
        }
    }
    for (i = TOTAL_STATION - 1; i >= 0; i--)
    {
        if (array[2][i] == 1 || array[1][i] == 1 || array[0][i] == 1)
        {
            counterclockwise = TOTAL_STATION - i;
            break;
        }
    }
    if (counterclockwise < clockwise)
    {
        Bus.direction = 2;
    }
    else if (counterclockwise >= clockwise)
    {
        Bus.direction = 1;
    }
    Bus.status = 0;
}

void SCAN::shunshizhen()
{
    if(bus_y==y_1){
        if(x_2-bus_x>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_x+=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else {
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            anim->setKeyValueAt(0.5,QPoint(x_2,y_1));
            bus_y+=distance-(x_2-bus_x);
            bus_x=x_2;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }
    else if(bus_x==x_2){
        if(y_2-bus_y>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y+=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else{
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y=y_2;
            bus_x-=distance-(y_2-bus_y);
            anim->setKeyValueAt(0.5,QPoint(x_2,y_2));
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }
    else if(bus_y==y_2){
        if(bus_x-x_1>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_x-=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else{
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y -= distance - (bus_x - x_1);
            bus_x=x_1;
            anim->setKeyValueAt(0.5,QPoint(x_1,y_2));
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }
    else if(bus_x==x_1){
        if(bus_y-y_1>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y-=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else{
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y=y_1;
            bus_x+=distance-(bus_y-y_1);
            anim->setKeyValueAt(0.5,QPoint(x_1,y_1));
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }

}
void SCAN::nishizhen(){
    if(bus_y==y_1){
        if(bus_x-x_1>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_x-=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else {
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            anim->setKeyValueAt(0.5,QPoint(x_1,y_1));
            bus_y+=distance-(bus_x-x_1);
            bus_x=x_1;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }
    else if(bus_x==x_1){
        if(y_2-bus_y>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y+=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else{
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_x+=distance-(y_2-bus_y);
            bus_y=y_2;
            anim->setKeyValueAt(0.5,QPoint(x_1,y_2));
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }
    else if(bus_y==y_2){
        if(x_2-bus_x>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_x+=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else{
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y -= distance - (x_2-bus_x);
            bus_x=x_2;
            anim->setKeyValueAt(0.5,QPoint(x_2,y_2));
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }
    else if(bus_x==x_2){
        if(bus_y-y_1>distance){
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_y-=distance;
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
        else{
            QPropertyAnimation *anim= new QPropertyAnimation(ui->label, "pos" );
            anim->setDuration(1000);
            anim->setStartValue(QPoint(bus_x,bus_y));
            bus_x-=distance-(bus_y-y_1-3); //这点是为了让图标对齐
            bus_y=y_1;
            anim->setKeyValueAt(0.5,QPoint(x_2,y_1));
            anim->setEndValue(QPoint(bus_x,bus_y));
            anim->start();
        }
    }


}
//析构函数
SCAN::~SCAN()
{
    delete ui;
}
